package org.vsg.stock.core.indicator.coordinate.processor;

import java.text.DecimalFormat;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;

import org.springframework.beans.factory.annotation.Autowired;
import org.vsg.stock.core.indicator.KLineStockIndicatorModel;
import org.vsg.stock.core.indicator.ZigIndicator;
import org.vsg.stock.core.indicator.coordinate.CoordinateContext;
import org.vsg.stock.core.indicator.coordinate.CoordinatePoint;
import org.vsg.stock.core.indicator.coordinate.OriginalDataPoint;
import org.vsg.stock.core.indicator.coordinate.Processor;
import org.vsg.stock.core.indicator.coordinate.SimpleCoordinatePoint;
import org.vsg.stock.core.indicator.coordinate.UnitDefinition;
import org.vsg.stock.core.indicator.coordinate.shape.ShapeEquation;
import org.vsg.stock.core.indicator.kline.ZigIndicatorResultItem;
import org.vsg.stock.core.kline.DailyKLineStock;
import org.vsg.stock.core.utils.StockDateUtilExtension;

public class SimpleProcessor implements Processor<DailyKLineStock>{

	@Autowired
	private StockDateUtilExtension stkDateUtilExtension;
	
	private DecimalFormat df = new DecimalFormat("0.0");
	
	/**
	 * @param context
	 * @param dataList
	 * @return 
	 * 
	 * 
	 */
	@Override
	public List<ShapeEquation> process(CoordinateContext context, List<DailyKLineStock> dataList) {
		
		OriginalDataPoint originPoint = context.getOriginPoint();
		
		UnitDefinition udef = context.getUnitDefinition();
		
		List<CoordinatePoint> pointList =new ArrayList<CoordinatePoint>();
		
	
		for (DailyKLineStock kline : dataList) {
			
			// ---- get the x & y value ---
			double yDiff = kline.getLow() - originPoint.getYvalue();
			
			
			int cycleDays = stkDateUtilExtension.getDifferenceValue(context.getStockCode(),
					originPoint.getXvalue(), kline.getDate());
			
			
			// ---- count the unit value ---
			double y = yDiff / udef.getYUnit();
			y = Double.parseDouble( df.format( y ) );
			
			double x = cycleDays / udef.getXUnit();
			
			// --- set the CoordinatePoint ----
			SimpleCoordinatePoint coordinatePoint = new SimpleCoordinatePoint();
			coordinatePoint.setXvalue( x );
			coordinatePoint.setYvalue( y );
			
			pointList.add( coordinatePoint );
			
		}
		
		// --- get the zip top handle ---
		
		KLineStockIndicatorModel klineStkIndiModel = new KLineStockIndicatorModel(dataList ,KLineStockIndicatorModel.KLinePosition.HIGH);

		ZigIndicator zigInd = new ZigIndicator();
		zigInd.setThreshold( (double)4.3 );
		zigInd.setIndicatorModel( klineStkIndiModel );

		Map<String, java.io.Serializable > resultMap  = zigInd.calculate();
		
		// --- use one point value check ---
		List<ZigIndicatorResultItem> allItems = (List<ZigIndicatorResultItem>) resultMap.get( ZigIndicator.ALL_CREST );
	
		
		List<CoordinatePoint> pointHighList =new ArrayList<CoordinatePoint>();		
		
		DailyKLineStock dailyKLineStk = null;
		for (ZigIndicatorResultItem itm : allItems) {
			dailyKLineStk = (DailyKLineStock)itm.getAssoRef();
			
			System.out.println( dailyKLineStk );
			// ---- get the x & y value ---
			double yDiff = dailyKLineStk.getLow() - originPoint.getYvalue();
			
			
			int cycleDays = stkDateUtilExtension.getDifferenceValue(context.getStockCode(),
					originPoint.getXvalue(), dailyKLineStk.getDate());
			
			
			// ---- count the unit value ---
			double y = yDiff / udef.getYUnit();
			y = Double.parseDouble( df.format( y ) );
			
			double x = cycleDays / udef.getXUnit();
			
			// --- set the CoordinatePoint ----
			SimpleCoordinatePoint coordinatePoint = new SimpleCoordinatePoint();
			coordinatePoint.setXvalue( x );
			coordinatePoint.setYvalue( y );
			
			pointHighList.add( coordinatePoint );
		}
		
		buildLine(pointHighList);
		
		System.out.println( pointHighList.size() );
		
		
		return null;
	}
	
	
	private void buildLine(List<CoordinatePoint> pointList ) {
		
		// --- get the high point 
		
		int markHighIndex = -1;
		
		double tmpHigh = 0;
		CoordinatePoint point = null;
		for (int i = 0 ; i < pointList.size() ; i++) {
			point = pointList.get(i);
			if (point.getYvalue() > tmpHigh) {
				tmpHigh = point.getYvalue();
				markHighIndex = i;
			}			
		}
		/*
		LinePattern linePattern = new UpwardTrackPressureLine();
		
		linePattern.setData( pointList );
		boolean matchResult = linePattern.matchAndAnalyze() ; 
		System.out.println( linePattern.getShapeCode() ) ;
		System.out.println( linePattern.getDescription() ) ;
		*/

		
	}
	
}
